/******************************************************************************
 * Student Name: Ofri Keidar
 * Exercise Name: Ex2
 * File Description: Class Course's interface
 ******************************************************************************/

#ifndef COURSE_H_
#define COURSE_H_
#include "StudentLinkedList.h"
#include "Lecturer.h"

class Course {

private:
	const int m_courseNumber; // course number
	const Lecturer* m_lecturer; // pointer to course lecturer
	StudentLinkedList* m_studentInCourse; // list of students who are registered to the course
	const StudentLinkedList& m_studentDataBase; // list of all existing students

	/***************************************************************************************
	 * function name: Course(const Course& course )
	 * The Input: Course to be copied
	 * The output: None
	 * The Function operation: The copy constructor is private and an empty-implementation
	 * 						   because course objects should not be sent to functions
	 * 						   by value
	 ***************************************************************************************/
	Course(const Course& course): m_courseNumber(course.m_courseNumber), m_lecturer(course.m_lecturer), m_studentDataBase(course.m_studentDataBase) {}

public:

	/***************************************************************************************
	 * function name: Course(const int courseNumber, const Lecturer* lecturer, const StudentLinkedList& studentDataBase)
	 * The Input: New course's attributes- number, lecturer and student database (list of
	 * 			  all students)
	 * The output: None
	 * The Function operation: Creates a new course with given attributes.
	 ***************************************************************************************/
	Course(const int courseNumber, const Lecturer* lecturer, const StudentLinkedList& studentDataBase);

	/***************************************************************************************
	 * function name: ~Course()
	 * The Input: None
	 * The output: None
	 * The Function operation: Deletes the course but does not delete the student
	 * 				           objects which are registered to the course or the lecturer
	 ***************************************************************************************/
	~Course();

	/***************************************************************************************
	 * function name: addStudent(const int numOfStudents, int** idList)
	 * The Input: Number of students to add and a list of their id's
	 * The output: Number of students who were not added
	 * The Function operation: For each given id, if there is not a student with the same
	 * 						   id, it adds the student. idList is a 2-dimensional array
	 * 						   that its first column is idList and the second is adding
	 * 						   result- True if student was added and False if not
	 ***************************************************************************************/
	int addStudent(const int numOfStudents, int** idList);

	/****************************************************************************************
	 * function name: getLecturerID()
	 * The Input: None
	 * The output: Id of course's lecturer
	 * The Function operation: Returns id attribute of course's lecturer, using lecturer's
	 * 					       getID method. Method does not change the object
	 ****************************************************************************************/
	int getLecturerID() const {return m_lecturer->getID();}

	/****************************************************************************************
	 * function name: getLecturerName()
	 * The Input: None
	 * The output: Name of course's lecturer
	 * The Function operation: Returns name attribute of course's lecturer, using lecturer's
	 * 					       getName method. Method does not change the object
	 ****************************************************************************************/
	string getLecturerName() const {return m_lecturer->getName();}

	/****************************************************************************************
	 * function name: getCourseNumber()
	 * The Input: None
	 * The output: Course's id
	 * The Function operation: Returns number attribute of course, without changing the object
	 ****************************************************************************************/
	int getCourseNumber() const {return m_courseNumber;}

	/***************************************************************************************
	 * function name: initStudentsInCourseCurr()
	 * The Input: None
	 * The output: None
	 * The Function operation: Sets list of registered students current node pointer to
	 * 					       list's head. This is done by using students list's method
	 * 					       to initialize the current node pointer
	 ***************************************************************************************/
	void initStudentsInCourseCurr() {m_studentInCourse->initCurrent();};

	/***************************************************************************************
	 * function name: incrmntStudentsInCourseCurr()
	 * The Input: None
	 * The output: False if registered students list end is reached, True if not
	 * The Function operation: Increments current node pointer. If points at lists end
	 * 			   returned value is False, otherwise True. This is done by using students
	 * 			   list's method to increment the current node pointer
	 ***************************************************************************************/
	bool incrmntStudentsInCourseCurr() {return m_studentInCourse->incrmntCurrent();}

	/***************************************************************************************
	 * function name: getStudentsInCourseCurrID()
	 * The Input: None
	 * The output: Id of student which current node in registered students list pointer points at.
	 * 	           If current node points at no student, ID_ERROR_VAL is returned
	 * The Function operation: Checks if student pointer is NULL. If so, returned ID_ERROR_VAL,
	 *			   otherwise returns the id. The method does not change the object and uses
	 *			   list's method to get current node's student data's id
	 ***************************************************************************************/
	int getStudentsInCourseCurrID() const {return m_studentInCourse->getCurrentID();}

	/***************************************************************************************
	 * function name: getStudentsInCourseCurrName()
	 * The Input: None
	 * The output: Name of student which current node in registered students list pointer points at.
	 * 	           If current node points at no student, NAME_ERROR_VAL is returned
	 * The Function operation: Checks if student pointer is NULL. If so, returned ID_ERROR_VAL,
	 *			   otherwise returns the id. The method does not change the object and uses
	 *			   list's method to get current node's student data's id
	 ***************************************************************************************/
	string getStudentsInCourseCurrName() const {return m_studentInCourse->getCurrentName();}

	/***************************************************************************************
	 * function name: getCurrentStudent()
	 * The Input: None
	 * The output: A pointer that registered students list's current node points at
	 * The Function operation: Uses registered student's list method in order to get pointer
	 * 						   to the student being pointed by current node pointer
	 ***************************************************************************************/
	Student* getCurrentStudent() const {return m_studentInCourse->getCurrentStudent();}

	/***************************************************************************************
	 * function name: getStudentsInCourse()
	 * The Input: None
	 * The output: A pointer to registered students list
	 * The Function operation: Returns the attribute of registered students list pointer
	 ***************************************************************************************/
	StudentLinkedList* getStudentsInCourse() const {return m_studentInCourse;}
};


#endif
